﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace FySystem.IOTFlow
{
    /// <summary>
    /// 写入数据，然后按照块将数据取出来，比如有10w条数据要按照每次1000条存入数据，那就需要1次取1000条，直到取完为止；
    /// 这个类只是返回一个开始和结束的索引，不返回实际的数据；
    /// 写这个类的原因是，每次都手写比较容易出错；
    /// 使用示例：
    /// int count = 96;
    /// BlockT bl = new BlockT(count, 10);
    /// do
    /// {
    ///     Console.WriteLine($"开始索引：{bl.StartIndex}，结束索引：{bl.EndIndex}");
    /// }
    /// while (bl.MoveNext()) ;
    /// </summary>
    public class BlockT
    {
        private int _maxIndex = 0;
        private int _block = 0;

        /// <summary>
        /// 开始索引
        /// </summary>
        public int StartIndex { get; private set; } = 0;
        /// <summary>
        /// 结束索引
        /// </summary>
        public int EndIndex { get; private set; } = 0;

        /// <summary>
        /// 构造
        /// </summary>
        /// <param name="count"></param>
        /// <param name="block"></param>
        public BlockT(int count,int block)
        {
            try
            {
                if (count <= 0)
                    throw new Exception("count不能小于1");
                if (block <= 0)
                    throw new Exception("block不能小于1");

                _maxIndex = count - 1;
                _block = block - 1;

                ResetIndex();
            }
            catch (Exception)
            {
                throw;
            }
        }

        /// <summary>
        /// 重置索引
        /// </summary>
        public void ResetIndex()
        {
            StartIndex = 0;
            EndIndex = _block;
            if (EndIndex > _maxIndex)
                EndIndex = _maxIndex;
        }

        /// <summary>
        /// 将索引往后移动一个块，调用该函数之后，StartIndex和EndIndex的值会相应变化；
        /// </summary>
        /// <returns>当索引超出了范围，返回false，否则返回true</returns>
        public bool MoveNext()
        {
            bool res = false;
            try
            {
                if (EndIndex >= _maxIndex)
                    return res;

                StartIndex += _block + 1;
                EndIndex = StartIndex + _block;
                if (EndIndex > _maxIndex)
                    EndIndex = _maxIndex;

                res = true;
            }
            catch (Exception)
            {
                throw;
            }
            return res;
        }
    }
}
